#!/usr/bin/env node

/**
 * 数据库备份脚本
 * Database Backup Script
 */

const path = require('path');
const BackupService = require('../server/services/backup');
const logger = require('../server/utils/logger');

// 设置进程标题
process.title = 'personal-cloud-notes-backup';

/**
 * 主备份函数
 * Main backup function
 */
async function main() {
  const backupService = new BackupService();
  
  try {
    console.log('='.repeat(60));
    console.log('Personal Cloud Notes - Database Backup');
    console.log('个人云笔记 - 数据库备份');
    console.log('='.repeat(60));
    console.log(`Start time: ${new Date().toISOString()}`);
    console.log('');

    // 执行备份
    const result = await backupService.performBackup();
    
    console.log('✅ Backup completed successfully!');
    console.log('');
    console.log('Backup Details:');
    console.log(`  File: ${result.backup.fileName}`);
    console.log(`  Size: ${backupService.formatFileSize(result.backup.size)}`);
    console.log(`  Path: ${result.backup.filePath}`);
    console.log('');
    
    if (result.cleanup.deletedCount > 0) {
      console.log('Cleanup Results:');
      console.log(`  Deleted backups: ${result.cleanup.deletedCount}`);
      console.log(`  Freed space: ${backupService.formatFileSize(result.cleanup.deletedSize)}`);
      console.log('');
    }

    // 显示备份统计
    const stats = await backupService.getBackupStats();
    console.log('Backup Statistics:');
    console.log(`  Total backups: ${stats.totalBackups}`);
    console.log(`  Total size: ${backupService.formatFileSize(stats.totalSize)}`);
    console.log(`  Average size: ${backupService.formatFileSize(stats.averageSize)}`);
    if (stats.oldestBackup) {
      console.log(`  Oldest backup: ${stats.oldestBackup.toISOString()}`);
    }
    if (stats.newestBackup) {
      console.log(`  Newest backup: ${stats.newestBackup.toISOString()}`);
    }
    
    console.log('');
    console.log(`End time: ${new Date().toISOString()}`);
    console.log('='.repeat(60));
    
    process.exit(0);
  } catch (error) {
    console.error('❌ Backup failed!');
    console.error('Error:', error.message);
    console.error('');
    console.error('Stack trace:');
    console.error(error.stack);
    
    logger.error('Backup script failed:', error);
    process.exit(1);
  }
}

/**
 * 处理命令行参数
 * Handle command line arguments
 */
function handleArguments() {
  const args = process.argv.slice(2);
  
  if (args.includes('--help') || args.includes('-h')) {
    console.log('Personal Cloud Notes - Database Backup Script');
    console.log('');
    console.log('Usage:');
    console.log('  node scripts/backup.js [options]');
    console.log('  npm run backup [options]');
    console.log('');
    console.log('Options:');
    console.log('  --help, -h     Show this help message');
    console.log('  --version, -v  Show version information');
    console.log('  --stats, -s    Show backup statistics only');
    console.log('  --list, -l     List all backups');
    console.log('  --verify FILE  Verify backup file integrity');
    console.log('  --cleanup      Clean expired backups only');
    console.log('');
    console.log('Examples:');
    console.log('  node scripts/backup.js                    # Create new backup');
    console.log('  node scripts/backup.js --stats            # Show statistics');
    console.log('  node scripts/backup.js --list             # List all backups');
    console.log('  node scripts/backup.js --cleanup          # Clean expired backups');
    console.log('  node scripts/backup.js --verify backup.sql # Verify backup file');
    process.exit(0);
  }
  
  if (args.includes('--version') || args.includes('-v')) {
    const packageJson = require('../package.json');
    console.log(`${packageJson.name} v${packageJson.version}`);
    process.exit(0);
  }
  
  return args;
}

/**
 * 显示备份统计
 * Show backup statistics
 */
async function showStats() {
  const backupService = new BackupService();
  
  try {
    const stats = await backupService.getBackupStats();
    
    console.log('Backup Statistics:');
    console.log('='.repeat(40));
    console.log(`Total backups: ${stats.totalBackups}`);
    console.log(`Total size: ${backupService.formatFileSize(stats.totalSize)}`);
    
    if (stats.totalBackups > 0) {
      console.log(`Average size: ${backupService.formatFileSize(stats.averageSize)}`);
      console.log(`Oldest backup: ${stats.oldestBackup.toISOString()}`);
      console.log(`Newest backup: ${stats.newestBackup.toISOString()}`);
    }
    
    process.exit(0);
  } catch (error) {
    console.error('Failed to get backup statistics:', error.message);
    process.exit(1);
  }
}

/**
 * 列出所有备份
 * List all backups
 */
async function listBackups() {
  const backupService = new BackupService();
  
  try {
    const backups = await backupService.getBackupList();
    
    console.log('Available Backups:');
    console.log('='.repeat(80));
    
    if (backups.length === 0) {
      console.log('No backups found.');
      process.exit(0);
    }
    
    console.log('File Name'.padEnd(35) + 'Size'.padEnd(12) + 'Created At');
    console.log('-'.repeat(80));
    
    for (const backup of backups) {
      const fileName = backup.fileName.padEnd(35);
      const size = backupService.formatFileSize(backup.size).padEnd(12);
      const createdAt = backup.createdAt.toISOString();
      
      console.log(`${fileName}${size}${createdAt}`);
    }
    
    process.exit(0);
  } catch (error) {
    console.error('Failed to list backups:', error.message);
    process.exit(1);
  }
}

/**
 * 验证备份文件
 * Verify backup file
 */
async function verifyBackup(fileName) {
  const backupService = new BackupService();
  
  try {
    const backupPath = path.resolve(fileName);
    const result = await backupService.verifyBackupIntegrity(backupPath);
    
    console.log(`Verifying backup: ${fileName}`);
    console.log('='.repeat(40));
    
    if (result.valid) {
      console.log('✅ Backup file is valid');
      console.log(`Size: ${backupService.formatFileSize(result.size)}`);
      console.log(`Created: ${result.createdAt.toISOString()}`);
    } else {
      console.log('❌ Backup file is invalid');
      console.log(`Error: ${result.error}`);
      process.exit(1);
    }
    
    process.exit(0);
  } catch (error) {
    console.error('Failed to verify backup:', error.message);
    process.exit(1);
  }
}

/**
 * 清理过期备份
 * Clean expired backups
 */
async function cleanupBackups() {
  const backupService = new BackupService();
  
  try {
    console.log('Cleaning expired backups...');
    const result = await backupService.cleanExpiredBackups();
    
    if (result.deletedCount > 0) {
      console.log(`✅ Cleaned ${result.deletedCount} expired backups`);
      console.log(`Freed space: ${backupService.formatFileSize(result.deletedSize)}`);
    } else {
      console.log('No expired backups to clean');
    }
    
    process.exit(0);
  } catch (error) {
    console.error('Failed to clean backups:', error.message);
    process.exit(1);
  }
}

// 处理未捕获的异常
process.on('uncaughtException', (error) => {
  console.error('Uncaught Exception:', error);
  logger.error('Uncaught exception in backup script:', error);
  process.exit(1);
});

process.on('unhandledRejection', (reason, promise) => {
  console.error('Unhandled Rejection at:', promise, 'reason:', reason);
  logger.error('Unhandled rejection in backup script:', reason);
  process.exit(1);
});

// 主程序入口
if (require.main === module) {
  const args = handleArguments();
  
  if (args.includes('--stats') || args.includes('-s')) {
    showStats();
  } else if (args.includes('--list') || args.includes('-l')) {
    listBackups();
  } else if (args.includes('--cleanup')) {
    cleanupBackups();
  } else if (args.includes('--verify')) {
    const fileIndex = args.findIndex(arg => arg === '--verify');
    const fileName = args[fileIndex + 1];
    if (!fileName) {
      console.error('Error: --verify requires a file name');
      process.exit(1);
    }
    verifyBackup(fileName);
  } else {
    main();
  }
}

module.exports = { main, showStats, listBackups, verifyBackup, cleanupBackups };